/// -----------------------------------------------------------------------------------------------------------
/// Module      :  SalesForceWCFAdapterConnectionUri.cs
/// Description :  This is the class for representing an adapter connection uri
/// -----------------------------------------------------------------------------------------------------------

#region Using Directives

using System;
using System.ComponentModel;
using System.Linq;
using System.Diagnostics;
using System.Drawing.Design;
using System.Windows.Forms;
using System.Windows.Forms.ComponentModel;
using System.Windows.Forms.Design;
using System.Xml;
using System.Xml.XPath;
using System.Xml.Linq;
using Microsoft.ServiceModel.Channels.Common;
using global::WCFLOBTalk.SalesForceWCF.Helpers;

#endregion

namespace WCFLOBTalk.SalesForceWCF
{
    public enum HostTypeEnum
    {
        c, u
    }

    public enum ProtocolTypesEnum
    {
        REST = 1, SOAP = 0
    }

    /// <summary>
    /// This is the class for building the SalesForceWCFAdapterConnectionUri
    /// </summary>
    public class SalesForceWCFAdapterConnectionUri : ConnectionUri
    {

        #region Custom Generated Fields

        // web service url could be broken down further...
        private string host = "test.salesforce.com";

        private string securityToken = "";

        private ProtocolTypesEnum protocolType = 0;   // 0 = SOAP, // 1 = REST

        private UriBuilder SFUriBuilder = new UriBuilder();

        #endregion Custom Generated Fields

        #region Constructors

        /// <summary>
        /// Initializes a new instance of the ConnectionUri class
        /// </summary>
        public SalesForceWCFAdapterConnectionUri() {
            Initialize(null);
        }

        /// <summary>
        /// Initializes a new instance of the ConnectionUri class with a Uri object
        /// </summary>
        public SalesForceWCFAdapterConnectionUri(Uri uri)
            : base()
        {
            Initialize(uri);
        }

        public void Initialize(Uri uri) {

            //MessageBox.Show("in uri initialize");

            if (uri != null)
            {
                ParseUri(uri);
            }
            else
            {
                this.SFUriBuilder = new UriBuilder(SalesForceWCFAdapter.SCHEME, "host");
            }
            //this.SFUriBuilder.Host = "";

        }

        #endregion Constructors

        #region Custom Generated Properties

        // make a custom ui editor for the LoadFromConfig

        private string configPath = "";

        [Editor(typeof(LoadFromConfigEditor), typeof(UITypeEditor))]
        public string LoadFromConfig
        {
            get
            {
                return this.configPath;
            }
            set
            {
                this.configPath = value;

                // Load the other properties using the path for the config file. 
                SetupLoadedConfigProperties(value);
            }
        }

        [Category("WSDL Properties")]
        public string Host
        {
            get
            {
                return this.host;
            }
            set
            {
                this.host = value;
            }
        }

      

        [Category("WSDL Properties")]
        public HostTypeEnum hostType { get; set; }

        [Category("WSDL Properties")]
        public string version { get; set; }


        [Category("Connection Properties")]
        public string SecurityToken
        {
            get
            {
                return this.securityToken;
            }
            set
            {
                this.securityToken = value;
            }
        }


        
        
        [Category("WSDL Properties")]
        public ProtocolTypesEnum ProtocolType
        {
            get
            {
                return this.protocolType;
            }
            set
            {
                this.protocolType = value;
            }
        }

        #endregion Custom Generated Properties

        #region ConnectionUri Members

        public void SetupLoadedConfigProperties(string path) {

           

                XmlDocument doc = new XmlDocument();
                doc.Load(path);

                XDocument d = XDocument.Parse(doc.OuterXml);
                var q1 = from c in d.Descendants(XName.Get("binding"))
                         where c.Attributes(XName.Get("name")).First().Value == "SalesForceWCFAdapterBinding"
                         select c;

                this.Host = q1.Attributes(XName.Get("host")).First().Value;
                this.hostType = (HostTypeEnum)Enum.Parse(typeof(HostTypeEnum), q1.Attributes(XName.Get("hostType")).First().Value);
                this.protocolType = (ProtocolTypesEnum)Enum.Parse(typeof(ProtocolTypesEnum), q1.Attributes(XName.Get("protocol")).First().Value);
                this.version = q1.Attributes(XName.Get("version")).First().Value;
                this.securityToken = q1.Attributes(XName.Get("securityToken")).First().Value;

            
        }


        /// <summary>
        /// Called to set the textbox after entering properties in the connect property grid.
        /// </summary>
        /// <returns></returns>
        private Uri BuildUri()
        {
            //MessageBox.Show("Building uri");

            try
            {

                this.SFUriBuilder.Scheme = SalesForceWCFAdapter.SCHEME;

                
                this.SFUriBuilder.Host = host;

                // build the path
                string protocol = "";
                if (this.protocolType == 0) { protocol = "Soap"; } else { protocol = "Rest"; }
                this.SFUriBuilder.Path = String.Format("services/{0}/{1}/{2}", protocol, this.hostType, this.version);
                this.SFUriBuilder.Query = "securityToken=" + this.securityToken;

                //StaticStoredObjects.Username = this.username;
                //StaticStoredObjects.Password = this.password;
                //StaticStoredObjects.SecurityToken = this.securityToken;

            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message + "\n" + e.StackTrace + "\n" + e.InnerException.StackTrace);
            }

            //MessageBox.Show("returning " + this.SFUriBuilder.Uri.ToString());

            return this.SFUriBuilder.Uri;
        }

        private void ValidateUri(Uri uri)
        {
            
            
        }

        private void ParseUri(Uri uri)
        {
            try
            {
                // refresh stored ones
                
                this.Host = uri.Host;
                this.securityToken = uri.Query.Replace("?securityToken=", "");
                //MessageBox.Show("In Parse Uri, uri: " + uri.ToString());


                for (int i = 0; i < uri.Segments.Length; i++)
                {
                    //MessageBox.Show("uri segment " + i.ToString() + " content: " + uri.Segments.GetValue(i).ToString());

                    string value = "";
                    switch (i)
                    {
                        case 2: // protocolType
                            value = uri.Segments.GetValue(2).ToString().Replace("/", "").ToUpper();
                            if (value == "SOAP") { this.protocolType = ProtocolTypesEnum.SOAP; } else { this.protocolType = ProtocolTypesEnum.REST; }
                            break;
                        case 3: // hostType
                            value = uri.Segments.GetValue(3).ToString().Replace("/", "").ToUpper();
                            if (value == "U") { this.hostType = HostTypeEnum.u; } else { this.hostType = HostTypeEnum.c; }
                            break;
                        case 4: // version
                            value = uri.Segments.GetValue(4).ToString();
                            this.version = value;
                            break;
                    }

                }
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message + "\n" + e.StackTrace + "\n" + e.InnerException.StackTrace);
            }

        }

        /// <summary>
        /// Getter and Setter for the Uri
        /// </summary>
        public override Uri Uri
        {
            get
            {
                //
                //TODO: Return the composed uri in valid format
                //
                return BuildUri();
            }
            set
            {
               SalesForceWCFAdapterUtilities.Trace.Trace(TraceEventType.Verbose, "SalesForceWCF", "In Uri Set with " + value);
                ValidateUri(value);
                ParseUri(value);
            }
        }

        #endregion ConnectionUri Members

    }
}